package com.android.fzmap.map;

import android.os.Bundle;

import com.google.android.maps.GeoPoint;

/**
 * 主要解决GPS偏移的问题
 * @author Administrator
 *
 */
public class GPSUtil {
	private static String QUERY_URL = "http://www.mapdigit.com/guidebeemap/offsetinchina.php";
	private static String METHOD_GET = "GET";
	
	/**
	 * 获取偏移值
	 * @param longitude
	 * @param latitude
	 * @param path
	 * @return
	 */
	public static GeoPoint adjustLoction(double latitude , double longitude) {

		Bundle params = new Bundle();
		params.putString("lng", String.valueOf(longitude));
		params.putString("lat", String.valueOf(latitude));
		String offsetString = HttpUtil.openUrl(QUERY_URL, METHOD_GET, params,
				 "UTF-8");
		int index = offsetString.indexOf(",");
		if (index > 0) {
			// 将坐标值转为18级相应的像素值
			double lngPixel = lonToPixel(longitude, 18);
			double latPixel = latToPixel(latitude, 18);
			// 获取偏移值
			String OffsetX = offsetString.substring(0, index).trim();
			String OffsetY = offsetString.substring(index + 1).trim();
			//加上偏移值
			double adjustLngPixel = lngPixel + Double.valueOf(OffsetX);
			double adjustLatPixel = latPixel + Double.valueOf(OffsetY);
			//由像素值再转为经纬度
			double adjustLng = pixelToLon(adjustLngPixel, 18);
			double adjustLat = pixelToLat(adjustLatPixel, 18);

			GeoPoint point =  new GeoPoint((int) (adjustLat * 1000000),
						(int) (adjustLng * 1000000));
			return  point;
		}
		//经验公式
		return new GeoPoint((int) ((latitude - 0.0025) * 1000000),
				(int) ((longitude + 0.0045) * 1000000));
	}

	/**
	 * 经度到像素X值
	 * 
	 * @param lng
	 * @param zoom
	 * @return
	 */
	public static double lonToPixel(double lng, int zoom) {
		return (lng + 180) * (256L << zoom) / 360;
	}

	/**
	 * 像素X到经度
	 * 
	 * @param pixelX
	 * @param zoom
	 * @return
	 */
	public static double pixelToLon(double pixelX, int zoom) {
		return pixelX * 360 / (256L << zoom) - 180;
	}

	/**
	 * 纬度到像素Y
	 * 
	 * @param lat
	 * @param zoom
	 * @return
	 */
	public static double latToPixel(double lat, int zoom) {
		double siny = Math.sin(lat * Math.PI / 180);
		double y = Math.log((1 + siny) / (1 - siny));
		return (128 << zoom) * (1 - y / (2 * Math.PI));
	}

	/**
	 * 像素Y到纬度
	 * 
	 * @param pixelY
	 * @param zoom
	 * @return
	 */
	public static double pixelToLat(double pixelY, int zoom) {
		double y = 2 * Math.PI * (1 - pixelY / (128 << zoom));
		double z = Math.pow(Math.E, y);
		double siny = (z - 1) / (z + 1);
		return Math.asin(siny) * 180 / Math.PI;
	}
	
	
}
